﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using AnguaRPGEngine.Library.Systems;

namespace AnguaRPGEngine.Library.Sockets
{
    public class PCClientSocket
    {
        public delegate void PCClientSocketErrorEventHandler(Guid SocketID, string Message);
        public delegate void PCClientMessageReceivedEventHandler(Guid SocketID, string Message);
        public delegate void PCClientSocketDisconnectEventHandler(Guid SocketID);
        public event PCClientMessageReceivedEventHandler OnMessageRecieved;
        public event PCClientSocketErrorEventHandler OnPCClientError;
        public event PCClientSocketDisconnectEventHandler OnPCClientDisconnect;
        private ClientSocket _Socket;
        public Guid SocketID;
        public PCClientSocket()
        {
            SocketID = Guid.NewGuid();
            _Socket = new ClientSocket();
            _Socket.OnConnectionTimeout += new ConnectionTimeoutEventHandler(_Socket_OnConnectionTimeout);
            _Socket.OnConnect += new ConnectEventHandler(_Socket_OnConnect);
            _Socket.OnDisconnect += new ClientClosingDelegate(_Socket_OnDisconnect);
            _Socket.OnGeneralError += new GeneralErrorEventHandler(_Socket_OnGeneralError);
            _Socket.OnReceive += new ReceiveEventHandler(_Socket_OnReceive);
            _Socket.OnSocketError += new SocketErrorEventHandler(_Socket_OnSocketError);
        }
        public PCClientSocket(ClientSocket Socket)
        {
            SocketID = Guid.NewGuid();
            _Socket = Socket;
            _Socket.OnConnectionTimeout += new ConnectionTimeoutEventHandler(_Socket_OnConnectionTimeout);
            _Socket.OnConnect += new ConnectEventHandler(_Socket_OnConnect);
            _Socket.OnDisconnect += new ClientClosingDelegate(_Socket_OnDisconnect);
            _Socket.OnGeneralError += new GeneralErrorEventHandler(_Socket_OnGeneralError);
            _Socket.OnReceive += new ReceiveEventHandler(_Socket_OnReceive);
            _Socket.OnSocketError += new SocketErrorEventHandler(_Socket_OnSocketError);
            _Socket.StartReceive();
        }
        void _Socket_OnSocketError(object sender, System.Net.Sockets.SocketException e)
        {
            if (OnPCClientError != null)
            {
                OnPCClientError(this.SocketID, e.Message);
            }
        }

        void _Socket_OnReceive(byte[] data, long numBytes)
        {
            string message = Tools.GetStringFromPackage(data, (int)numBytes);
            if (OnMessageRecieved != null)
            {
                OnMessageRecieved(this.SocketID, message);
            }
        }

        void _Socket_OnGeneralError(object sender, Exception e)
        {
            if (OnPCClientError != null)
            {
                OnPCClientError(this.SocketID, e.Message);
            }
        }

        public void SendMessage(byte[] package)
        {
            _Socket.Send(package);
        }
        void _Socket_OnDisconnect()
        {
            if (OnPCClientDisconnect != null)
            {
                OnPCClientDisconnect(this.SocketID);
            }
        }
        public void Stop()
        {
            _Socket.StopClient();
            _Socket.OnConnectionTimeout -= _Socket_OnConnectionTimeout;
            _Socket.OnConnect -= _Socket_OnConnect;
            _Socket.OnDisconnect -= _Socket_OnDisconnect;
            _Socket.OnGeneralError -= _Socket_OnGeneralError;
            _Socket.OnReceive -= _Socket_OnReceive;
            _Socket.OnSocketError -= _Socket_OnSocketError;
            _Socket.Dispose();
        }
        void _Socket_OnConnect()
        {
           // throw new NotImplementedException();
        }

        void _Socket_OnConnectionTimeout()
        {
          //  throw new NotImplementedException();
        }
        public void Connect(string HostIP, int HostPort)
        {
            _Socket.StartClient(HostIP, HostPort);
            _Socket.StartReceive();
        }
    }
}
